如何從數據中解讀,餐廳裡面需要多少個服務生? Licensed by Adobe Stock
Meiko:「誒,Jason,前兩天我們學會了 pandas ,我覺得其實運用 pandas 不是特別難,難的是要怎麼想到要對資料做什麼樣的處理?」
Jason:「坦白說是這樣沒錯,因為程式的語法就在那邊,如果你不會的話,就上網 Google 一下看更多案例。可是當你得到資料後,要看什麼數據?要怎麼解讀數據?那就是除了寫程式之外,另外一個重要的技術了!」
Meiko:「哈,你也這樣覺得?不過你不是跟餐廳老闆很熟,他應該就會跟你講他想要知道什麼了吧?」
Jason:「對啊,每個老闆都需要的基本能力,就是成本的觀念,進貨的成本、人事的成本、場地租金、水、店、瓦斯。還有現在連宣傳、行銷也都變得很重要了!」
Meiko:「你這樣一說,想起來開餐廳還真的蠻花錢的耶!」
Jason:「對啊,像我剛講的宣傳、行銷,老闆花的每一筆錢,當然都希望可以對收入帶來正面的影響!」
Meiko:「但我們這樣一聊起來,好像又會牽涉到很多東西,能不能從一個簡單的例子下手?」
Jason:「Okay,那我出一個簡單的情境題給你。你要怎麼判斷,餐廳的每個時段需要多少位服務生?」
Meiko:「每個時段需要多少的服務生?應該跟那個時段有多少訂單有關係吧?如果訂單數量多,表示該時段有很多的客人,如果數量少,餐廳就不需要那麼多服務生了,很合理吧!」
Jason:「沒錯,所以我們第一個就來看資料裡面是否有這樣的資訊。」
我大寶寶拉~請下載連結1 和連結2 這 2 個檔案。下載檔案後,再解壓縮,並且上傳到自己的 Colab 檔案上傳區,不知道怎麼做的話,可以參考Day-20上傳檔案的做法!
另外一補充一下連結 1 是在 Day-21,開檔讀檔,學會讀取檔並進行簡單計算(中) 有用到,連結 2 則是在Day-22,開檔讀檔,學會讀取檔並進行簡單計算(下)提到!記得要先看一下Day-23把連結 1 和連結 2 的檔案合併,才能繼續今天的課程內容唷!
Meiko:「這樣看起來,我們應該是要找到有時間的資訊,Day-22你已經跟我講特定的時段,可以知道有多少筆訂單了,感覺現在只要把時段都設定好,比如說從中午 12 點到晚上 12 點,每小時都切分成一個時段區間,就可以了!」
Jason:「每小時都切分,你會怎麼做?」
Meiko:「哈,我想得到要用特定時段,但有 12 個時段,難道要一個個寫?」
Jason:「你先把想法寫出來囉,資料分析可以有兩種角度去看,一個是程式運算的邏輯,還有另外一個能否找到商業價值,我覺得你可以先從找到商業價值開始!」
Meiko:「那你就不要怪我寫出很醜的程式碼囉,哈哈!我目前想到切割成 12 個時段只能先這樣做...」
from datetime import datetime, timedelta
d1 = datetime.strptime('10/1/2020 12:00 PM', '%m/%d/%Y %I:%M %p')
d2 = datetime.strptime('10/1/2020 1:00 PM', '%m/%d/%Y %I:%M %p')
d3 = datetime.strptime('10/1/2020 2:00 PM', '%m/%d/%Y %I:%M %p')
d4 = datetime.strptime('10/1/2020 3:00 PM', '%m/%d/%Y %I:%M %p')
d5 = datetime.strptime('10/1/2020 4:00 PM', '%m/%d/%Y %I:%M %p')
d6 = datetime.strptime('10/1/2020 5:00 PM', '%m/%d/%Y %I:%M %p')
d7 = datetime.strptime('10/1/2020 6:00 PM', '%m/%d/%Y %I:%M %p')
d8 = datetime.strptime('10/1/2020 7:00 PM', '%m/%d/%Y %I:%M %p')
d9 = datetime.strptime('10/1/2020 8:00 PM', '%m/%d/%Y %I:%M %p')
d10 = datetime.strptime('10/1/2020 9:00 PM', '%m/%d/%Y %I:%M %p')
d11 = datetime.strptime('10/1/2020 10:00 PM', '%m/%d/%Y %I:%M %p')
d12 = datetime.strptime('10/1/2020 11:00 PM', '%m/%d/%Y %I:%M %p')
d13 = datetime.strptime('10/1/2020 11:59 PM', '%m/%d/%Y %I:%M %p')
date_mask1 = (pdTotal['time'] < d2) & (pdTotal['time'] > d1)
date_mask2 = (pdTotal['time'] < d3) & (pdTotal['time'] > d2)
date_mask3 = (pdTotal['time'] < d4) & (pdTotal['time'] > d3)
date_mask4 = (pdTotal['time'] < d5) & (pdTotal['time'] > d4)
date_mask5 = (pdTotal['time'] < d6) & (pdTotal['time'] > d5)
date_mask6 = (pdTotal['time'] < d7) & (pdTotal['time'] > d6)
date_mask7 = (pdTotal['time'] < d8) & (pdTotal['time'] > d7)
date_mask8 = (pdTotal['time'] < d9) & (pdTotal['time'] > d8)
date_mask9 = (pdTotal['time'] < d10) & (pdTotal['time'] > d9)
date_mask10 = (pdTotal['time'] < d11) & (pdTotal['time'] > d10)
date_mask11 = (pdTotal['time'] < d12) & (pdTotal['time'] > d11)
date_mask12 = (pdTotal['time'] < d13) & (pdTotal['time'] > d12)
dateMaskList=[date_mask1,date_mask2,date_mask3,date_mask4,date_mask5,date_mask6,date_mask7,
date_mask8,date_mask9,date_mask10,date_mask11,date_mask12]
lenList=list()
for i in range(len(dateMaskList)):
date_mask=dateMaskList[i]
pdTotalResult = pdTotal[date_mask]
lenList.append(len(pdTotalResult))
print ("--------")
print (lenList)
Jason:「Okay 啊,你講一下上面這段程式碼你做了什麼?」
Meiko:「跟你昨天講的切割時段很像,我只是繼續應用這個做法,最上面 d1
~d13
就是在設定時間區間,接下來date_mask1
~date_mask12
則是設定條件,唯一不同的是因為我們總共有 12 個條件,所以我想說把這些條件全部都放到一個dateMaskList
裡面,這樣我就可以用for-loop
跑過所有的條件!」
Jason:「不錯耶,儘管條件設定的部分,還沒想到更快的做法,可是你已經在搜尋時間區間內有多少訂單用上for-loop
了!」
Meiko:「對啊,為了知道最後的結果,我另外在for-loop
前設定了一個lenList
,然後在for-loop
中,得到pdTotalResult
之後,把這個結果.append()
到lenList
。像這樣」
[8, 4, 9, 8, 7, 5, 15, 9, 13, 7, 8, 7]
Jason:「不過,這段結果代表的意思是?」
Meiko:「歐,Jason 你都沒注意在聽我講前面的作法,我不是把這天的資料報表,切割成 12 個時段嗎?所以每個數字,就代表那個時段有多少筆訂單囉!」
Jason:「哈,我故意考你的拉,我想知道你能否馬上說出來這段程式的商業邏輯是什麼?」
Meiko:「歐,早說麻!哈,我有個問題,資料整理出來之後,要怎麼很快知道這筆資料的有什麼特性?」
Jaosn:「你記得我們有講過 pandas 可以用.describe()
嗎?」
Meiko:「可是,我上面做出來的結果是 list 怎麼辦?」
Jason:「我們可以先把 list 轉換成 pandas 能夠運作的DataFrame
,像這樣」
pdLenList=pd.DataFrame(lenList)
pdLenList.describe()
Jason:「然後我們就可以用.describe()
很快知道,這筆資料的最大、最小、平均值和中位數的資訊囉!」
Meiko:「歐,這樣蠻棒的!如果結合原本的lenList
資訊,這樣看來,這天晚餐的 6:00 PM ~7:00 PM 的時間,是訂單出現最大值的時段有 15 筆訂單,然後 1:00 PM ~ 2:00 PM 是訂單出現最小值的時段,只有 4 筆訂單。」
Jason:「你還有看到什麼嗎?」
Meiko:「我發現在 8:00 PM ~ 9:00 PM 的時間,訂單數量也滿多的!有 13 張訂單!」
Jason:「這蠻有趣的耶,雖然只有一天的銷售紀錄,但是你有沒有發現,你可以給老闆在服務生人員配置上給出什麼建議?」
Meiko:「這樣看來中午時段過了 1:00 Pm 之後,人力可以少一些,但是晚上 6:00 PM 之後,生意都會蠻好的,可能要多一點人才行!不過 9:00 PM 之後,應該變成宵夜場,好像人力的需求又少一些」
Jason:「我剛剛問了老闆,他說餐廳中午確實有比晚上少一位服務生,看來還蠻符合我們資料分析的結果!」
Meiko:「好棒唷!馬上就得到印證了!不過,我們好像才做了一點點的分析而已耶?」
Jason:「是啊,我們也許可以用一些圖表的方式,再去挖掘看能發現什麼...」
我大寶寶~拉,今天我們談到處理資料的商業邏輯,並且接續前一天利用時間的關係,設定條件找出餐廳在每個時段的訂單數量,發現在晚餐的時間訂單數量是比較多的狀況,那這樣也要確保當時有足夠的服務生人數,才不會讓來到餐廳的客人抱怨囉!接下來,我們會再介紹 Matplotlib 用圖表的方式,畫出資料間的關係...
你也可以試著想看看 Meiko 在今天寫的條件限制的地方,有沒有辦法加速或是用for-loop
來進行,就當作給大家練習囉!
歡迎登入留言跟我分享你的想法唷!(登入不麻煩,點一下 FB 登入就可以留言了!)
1.喜歡這樣方式學 Python 的朋友請留言『+1』
2.如果前面的內容忘記了,趕快看一下大寶寶這一系列的看對話學 Python 資料分析,用情境故事帶你入門的列表!就能夠繼續 Happy Coding 囉!
from datetime import datetime
def datetime_fun(time):
name = datetime.strptime('10/1/2020 ' + time + ' PM', '%m/%d/%Y %I:%M %p')
return name
def date_mask_fun(last_time,first_time):
return ((pdTotal['time'] < last_time) & (pdTotal['time'] > first_time))
d_list = ['d1','d2','d3','d4','d5','d6','d7','d8','d9','d10','d11','d12','d13']
dict_time = {}
pdTotalResult = []
for i in range(1,13):
if i == 12:
time = str(i-1) + ':59'
else:
time = str(i) + ':00'
dict_time[d_list[i]] = datetime_fun(time)
dict_time[d_list[0]] = datetime_fun('12:00')
for i in range(len(dict_time)):
if i <= 10:
date_mask = date_mask_fun(dict_time[d_list[i+1]], dict_time[d_list[i]])
pdTotalResult.append(len(pdTotal[date_mask]))
print(pdTotalResult)
[8, 4, 9, 8, 7, 5, 15, 9, 13, 7, 8]
花了一些時間理解,練習,然後簡化成這樣
謝謝